package cn.gs.serializable.serialize;

// @author gs
import cn.gs.serializable.annotation.NType;
import cn.gs.serializable.entity.IEntity;
import cn.gs.serializable.entity.OneEntity;
import cn.gs.serializable.serialize.ISerialize;
import cn.gs.serializable.serialize.SerializeController;
import java.math.BigDecimal;
import java.math.BigInteger;
import java.util.regex.Pattern;

public class NumberSerialize implements ISerialize {

    static final Pattern pattern = Pattern.compile("(-)?(\\d*\\.\\d+|\\d+)((e|E)(\\d)+)?");

    @Override
    public <T> T toObj(cn.gs.serializable.serialize.ISerialize ctrl, IEntity from, Class<T> clazz) {
        if (!(from instanceof OneEntity)) {
            return null;
        }
        String t = ((OneEntity) from).getValue();
        if (!pattern.matcher(t).matches() || ((OneEntity) from).isQuote()) {
            return null;
        }
        if (clazz == null) {
            if (t.indexOf(".") >= 0) {
                return (T) Double.valueOf(t);
            } else {
                return (T) Integer.valueOf(t);
            }
        }
        if (clazz.isAssignableFrom(Double.class) || clazz == double.class) {
            return (T) Double.valueOf(t);
        } else if (clazz.isAssignableFrom(Float.class) || clazz == float.class) {
            return (T) Float.valueOf(t);
        } else if (clazz.isAssignableFrom(Long.class) || clazz == long.class) {
            return (T) Long.valueOf(t);
        } else if (clazz.isAssignableFrom(Integer.class) || clazz == int.class) {
            return (T) Integer.valueOf(t);
        } else if (clazz.isAssignableFrom(Short.class) || clazz == short.class) {
            return (T) Short.valueOf(t);
        } else if (clazz.isAssignableFrom(Byte.class) || clazz == byte.class) {
            return (T) Byte.valueOf(t);
        } else if (clazz.isAssignableFrom(BigInteger.class)) {
            return (T) new BigInteger(t, 10);
        } else if (clazz.isAssignableFrom(BigDecimal.class)) {
            return (T) new BigDecimal(t);
        } else {
            return null;
        }
    }

    @Override
    public IEntity fromObj(ISerialize ctrl, Object o) {
        if (o == null) {
            return null;
        }
        if (o instanceof Double || o instanceof Float
                || o instanceof Long || o instanceof Integer
                || o instanceof Short || o instanceof Byte
                || o instanceof BigInteger || o instanceof BigDecimal) {
            return new OneEntity(o.toString());
        } else {
            return null;
        }
    }
}
